package com.zzh.custom;

import android.animation.ValueAnimator;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.os.Build;
import android.util.AttributeSet;
import android.view.View;

import androidx.annotation.Nullable;
import androidx.annotation.RequiresApi;

import com.zzh.tools.system.ToolScreen;
import com.zzh.tools.utils.ToolLog;


/**
 * @author zhangzhihao
 * @email zhangzhihao@gongjiangren.net
 * @date 2021-02-07
 * @desc
 */
public class SwitchView extends View {

    public interface OnSelectSwitchListener {
        void onSelect(boolean status);
    }

    private int mMinHeight;
    private int mMinWidth;

    private int mSwitchMargin;

    private boolean mSelectStatus;
    private OnSelectSwitchListener mOnSelectSwitchListener;

    // 背景
    private Paint selectPaint;
    private Paint unSelectPaint;
    // switch 状态
    private Paint mSwitchPaint;


    public SwitchView(Context context) {
        this(context, null);
    }

    public SwitchView(Context context, @Nullable AttributeSet attrs) {
        this(context, attrs, -1);
    }

    public SwitchView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);

        init(context, attrs);

    }

    private void init(Context context, AttributeSet attrs) {
        config(context);
        selectPaint = new Paint();
        unSelectPaint = new Paint();
        mSwitchPaint = new Paint();
        // 设置颜色
        selectPaint.setColor(Color.parseColor("#0ac160"));
        unSelectPaint.setColor(Color.parseColor("#e9e9e9"));
        mSwitchPaint.setColor(Color.parseColor("#ffffff"));
        // 防止锯齿
        selectPaint.setAntiAlias(true);
        unSelectPaint.setAntiAlias(true);
        mSwitchPaint.setAntiAlias(true);
        // 防止抖动
        selectPaint.setDither(true);
        unSelectPaint.setDither(true);
        mSwitchPaint.setDither(true);


        super.setOnClickListener(v -> {
            if (!isFastClick()) {
                if (setSelectStatus(!mSelectStatus, true)) {
                    if (mOnSelectSwitchListener != null) {
                        mOnSelectSwitchListener.onSelect(mSelectStatus);
                    }
                }
            }
        });

        mSelectStatus = false;
        mAnimatorValue = 1;
    }

    private void config(Context context) {
        mMinHeight = ToolScreen.dip2px(context, 30);
        mMinWidth = ToolScreen.dip2px(context, 50);
        mSwitchMargin = ToolScreen.dip2px(context, 2);
    }

    private long lastClickTime;

    private boolean isFastClick() {
        boolean flag = true;
        long curClickTime = System.currentTimeMillis();
        if ((curClickTime - lastClickTime) >= 500L) {
            flag = false;
            lastClickTime = curClickTime;
        }
        return flag;
    }

    @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        drawBg(canvas);
        drawSwith(canvas);
    }

    private void drawSwith(Canvas canvas) {
        float left = getPaddingLeft();
        float top = getPaddingTop();
        float bottom = mHeight - getPaddingBottom();
        float right = mWidth - getPaddingRight();
        float radius = ((bottom - top) - mSwitchMargin * 2) / 2;

        float difference = right - left - mSwitchMargin * 2 - radius * 2;

        if (mSelectStatus) {
            canvas.drawCircle(right - mSwitchMargin - radius - (1 - mAnimatorValue) * difference,
                    top + mSwitchMargin + radius, radius, mSwitchPaint);
        } else {
            canvas.drawCircle(left + mSwitchMargin + radius + (1 - mAnimatorValue) * difference,
                    top + mSwitchMargin + radius, radius, mSwitchPaint);
        }
    }

    @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
    private void drawBg(Canvas canvas) {
        float left = getPaddingLeft();
        float top = getPaddingTop();
        float bottom = mHeight - getPaddingBottom();
        float right = mWidth - getPaddingRight();
        float round = (bottom - top) / 2;

        canvas.drawRoundRect(left, top, right, bottom, round, round, mSelectStatus ? selectPaint : unSelectPaint);
    }

    public void setSelectStatus(boolean selectStatus) {
        setSelectStatus(selectStatus, false);
    }

    private boolean setSelectStatus(boolean selectStatus, boolean isAnimation) {
        if (mSelectStatus == selectStatus) {
            return false;
        }
        mSelectStatus = selectStatus;
        if (isAnimation) {
            mAnimatorValue = 0;
            performAnimation();
        } else {
            clearValueAnimation();
            mAnimatorValue = 1;
            invalidate();
        }
        return true;
    }

    private ValueAnimator mValueAnimator;
    private float mAnimatorValue;

    private void performAnimation() {
        clearValueAnimation();
        mValueAnimator = ValueAnimator.ofFloat(0f, 1f);
        mValueAnimator.setDuration(500);
        mValueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                mAnimatorValue = (float) animation.getAnimatedValue();
                ToolLog.i("zzh", ">>>>>>>" + mAnimatorValue);
                invalidate();
            }
        });
        mValueAnimator.start();
    }

    private void clearValueAnimation() {
        if (mValueAnimator != null) {
            if (mValueAnimator.isRunning()) {
                mValueAnimator.removeAllUpdateListeners();
                mValueAnimator.cancel();
            }
            mValueAnimator = null;
        }
    }

    @Override
    public void setOnClickListener(OnClickListener onClickListener) {
        ToolLog.i("zzh", "不做任何处理 不允许有外部的点击事件");
    }

    public void setOnSelectSwitchListener(OnSelectSwitchListener onSelectSwitchListener) {
        mOnSelectSwitchListener = onSelectSwitchListener;
    }

    private int mWidth;
    private int mHeight;

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        /**
         * 设置宽度
         */
        int specMode = MeasureSpec.getMode(widthMeasureSpec);
        int specSize = MeasureSpec.getSize(widthMeasureSpec);
        if (specMode == MeasureSpec.EXACTLY) {
            // match_parent , accurate
            mWidth = specSize;
        } else {
            if (specMode == MeasureSpec.AT_MOST) {
                // wrap_content
                mWidth = Math.min(mMinWidth, specSize);
            } else {
                mWidth = mMinWidth;
            }
        }
        /***
         * 设置高度
         */
        specMode = MeasureSpec.getMode(heightMeasureSpec);
        specSize = MeasureSpec.getSize(heightMeasureSpec);
        if (specMode == MeasureSpec.EXACTLY) {
            // match_parent , accurate
            mHeight = specSize;
        } else {
            if (specMode == MeasureSpec.AT_MOST) {
                // wrap_content
                mHeight = Math.min(mMinHeight, specSize);
            } else {
                mHeight = mMinHeight;
            }
        }
        setMeasuredDimension(mWidth, mHeight);
    }


}
